public class Test {
//    5.定义凯撒加密器和解密器函数，接收明文字符串参数，返回密文字符串结果。
//    加密"I LOVE YOU FOREVER",解密"L ORYH BRX IRUHYHU"
//    恺撒密码的替换方法是通过排列明文和密文字母表，密文字母表示通过将明文字母表向左或向右移动一个固定数目的位置。例如，当偏移量是左移3的时候（解密时的密钥就是3）：
//
//    明文字母表：ABCDEFGHIJKLMNOPQRSTUVWXYZ
//    密文字母表：DEFGHIJKLMNOPQRSTUVWXYZABC
//
//    使用时，加密者查找明文字母表中需要加密的消息中的每一个字母所在位置，并且写下密文字母表中对应的字母。需要解密的人则根据事先已知的密钥反过来操作，得到原来的明文。例如：
//
//    明文：THE QUICK BROWN FOX JUMPS OVER THE LAZY DOG
//    密文：WKH TXLFN EURZQ IRA MXPSV RYHU WKH ODCB GRJ

    // 加密函数
    public static String encrypt(String plaintext, int shift) {
        StringBuilder ciphertext = new StringBuilder();
        // 遍历明文中的每一个字符
        for (int i = 0; i < plaintext.length(); i++) {
            char ch = plaintext.charAt(i);
            // 只对字母进行加密，忽略其他字符
            if (Character.isLetter(ch)) {
                // 获取字符的大写形式
                char base = Character.isUpperCase(ch) ? 'A' : 'a';
                // 对字符进行偏移加密
                ch = (char) ((ch - base + shift) % 26 + base);
            }
            // 将加密后的字符添加到密文中
            ciphertext.append(ch);
        }
        return ciphertext.toString();
    }

    // 解密函数
    public static String decrypt(String ciphertext, int shift) {
        // 解密实际上就是加密的逆过程，只需要将偏移量取反即可
        return encrypt(ciphertext, 26 - shift);
    }

    // 测试函数
    public static void main(String[] args) {
        // 定义明文和偏移量
        String plaintext = "I NEVER FORGET";
        int shift = 3; // 偏移量为3

        // 加密明文
        String encrypted = encrypt(plaintext, shift);
        System.out.println("加密后：" + encrypted); // 打印密文

        // 解密密文
        String decrypted = decrypt(encrypted, shift);
        System.out.println("解密后：" + decrypted); // 打印解密后的明文
    }

    //4.打印12345678所有的排列方式，共8!种。
//            12345678
//            12345687
//            12345768
//            12345786
//            12345867
//            12345876
//            ........
//            87654321

        public static void printPermutations(int[] arr, int start, int end) {
            if (start == end) {
                for (int num : arr) {
                    System.out.print(num);
                }
                System.out.println();
            } else {
                for (int i = start; i <= end; i++) {
                    swap(arr, start, i);
                    printPermutations(arr, start + 1, end);
                    swap(arr, start, i);
                }
            }
        }

        private static void swap(int[] arr, int i, int j) {
            int temp = arr[i];
            arr[i] = arr[j];
            arr[j] = temp;
        }

        public static void main4(String[] args) {
            int[] arr = {1, 2, 3, 4, 5, 6, 7, 8};
            printPermutations(arr, 0, arr.length - 1);
        }

    //3.写一个函数sort冒泡排序，接受一个整数数组，返回数组排好序后的结果。
    // 并在main中定义三个数组，调用用此方法后打印出来。
    public static void bubbleSort(int[] arr){
        for (int i = 0; i < arr.length - 1; i++) {
            for (int j = 0; j < arr.length - i - 1; j++) {
                if(arr[j] > arr[j+1]){
                    int tmp = arr[j];
                    arr[j] = arr[j+1];
                    arr[j+1] =tmp;
                }
            }
        }
    }
    
    public static void main3(String[] args) {
        int[] arr1 = new int[]{3,4,1,25,7,4,245,141,23,6,45};
        int[] arr2 = new int[]{23,41,567,714,14,46,241,56};
        int[] arr3 = new int[]{123,4546,75,35,3,675,8};
        bubbleSort(arr1);
        bubbleSort(arr2);
        bubbleSort(arr3);
        for (int x: arr1) {
            System.out.print(x+" ");
        }
        System.out.println();
        for (int x: arr2) {
            System.out.print(x+" ");
        }
        System.out.println();
        for (int x: arr3) {
            System.out.print(x+" ");
        }
    }


    //2.定义一个方法sumDouble对数组double[]求和
    // 定义一个方法sumInt对数组int[]求和。并在main中调用
    public static double toSum(double[] arr){
        double sum = 0;
        for (int i = 0; i < arr.length; i++) {
            sum += arr[i];
        }
        return sum;
    }

    public static int toSum(int[] arr){
        int sum = 0;
        for (int i = 0; i < arr.length; i++) {
            sum += arr[i];
        }
        return sum;
    }

    public static void main2(String[] args) {
        double[] arr1 = new double[]{1.0,2.0,3.0,4.0,5.0};
        int[] arr2 = new int[]{1,2,3,4,5};

        double ret1 = toSum(arr1);
        int ret2 = toSum(arr2);

        System.out.println(ret1);
        System.out.println(ret2);
    }

    //1.写一个函数，计算两点(x1, y1)和(x2, y2)之间的距离。并在main中调用
    public static double toDistance(double x1,double y1,double x2,double y2){
        double x = x1 - x2,
                y = y1 - y2;
        double ret = Math.sqrt((Math.pow(x,2)+Math.pow(y,2)));
        return ret;
    }

    public static void main1(String[] args) {
        String ret = String.format("%.2f",toDistance(1.0,1.0,2.0,2.0));
        System.out.println(ret);
    }
}
